import dash
import dash_html_components as html
import dash_core_components as dcc
from dash.dependencies import Input, Output, State
import dash_bootstrap_components as dbc
import cv2
import numpy as np
import base64
from io import BytesIO
from PIL import Image
# Initialize the Dash app
app = dash.Dash(__name__, external_stylesheets=[dbc.themes.BOOTSTRAP])
app.layout = dbc.Container([
dbc.Row([
dbc.Col(html.H1("Dash with OpenCV Example"), className="mb-4")
]),
dbc.Row([
dbc.Col(dcc.Upload(
id='upload-image',
children=html.Div(['Drag and Drop or ', html.A('Select a File')]),
style={
'width': '100%', 'height': '60px', 'lineHeight': '60px',
'borderWidth': '1px', 'borderStyle': 'dashed', 'borderRadius': '5px',
'textAlign': 'center', 'margin': '10px'
},
multiple=False
), width=12)
]),
dbc.Row([
dbc.Col(html.Img(id='output-image'), width=12)
]),
dbc.Row([
dbc.Col(dbc.Button("Grayscale", id='grayscale-button', color='primary', className="mt-4"), width=3),
dbc.Col(dbc.Button("Blur", id='blur-button', color='secondary', className="mt-4"), width=3),
dbc.Col(dbc.Button("Edge Detection", id='edge-button', color='success', className="mt-4"), width=3),
dbc.Col(dbc.Button("Invert Colors", id='invert-button', color='danger', className="mt-4"), width=3)
])
], fluid=True)
def parse_contents(contents):
content_type, content_string = contents.split(',')
decoded = base64.b64decode(content_string)
image = Image.open(BytesIO(decoded))
return np.array(image)
def apply_grayscale(image):
gray_image = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
return cv2.cvtColor(gray_image, cv2.COLOR_GRAY2BGR)
def apply_blur(image):
return cv2.GaussianBlur(image, (15, 15), 0)
def apply_edge_detection(image):
edges = cv2.Canny(image, 100, 200)
return cv2.cvtColor(edges, cv2.COLOR_GRAY2BGR)
def apply_invert(image):
return cv2.bitwise_not(image)
@app.callback(
Output('output-image', 'src'),
[Input('upload-image', 'contents'),
Input('grayscale-button', 'n_clicks'),
Input('blur-button', 'n_clicks'),
Input('edge-button', 'n_clicks'),
Input('invert-button', 'n_clicks')],
[State('upload-image', 'contents')]
)
def update_output(contents, grayscale_n, blur_n, edge_n, invert_n, state_contents):
if contents is None:
raise dash.exceptions.PreventUpdate
image = parse_contents(state_contents)
ctx = dash.callback_context
if not ctx.triggered:
button_id = 'None'
else:
button_id = ctx.triggered[0]['prop_id'].split('.')[0]
if button_id == 'grayscale-button':
image = apply_grayscale(image)
elif button_id == 'blur-button':
image = apply_blur(image)
elif button_id == 'edge-button':
image = apply_edge_detection(image)
elif button_id == 'invert-button':
image = apply_invert(image)
_, buffer = cv2.imencode('.jpg', image)
encoded_image = base64.b64encode(buffer).decode('utf-8')
return f'data:image/jpeg;base64,{encoded_image}'
if __name__ == '__main__':
app.run_server(debug=True)